using System;
using System.Net.Http;
using System.Threading.Tasks;
using Microsoft.AspNetCore.SignalR.Client;
using WPF_MVVM_Test.MVVM_Model;

namespace WPF_MVVM_Test.Services
{
    /// <summary>
    /// 消息队列服务 - 简化版本
    /// 后端会处理MQ消息发送，前端只需要提交任务即可
    /// </summary>
    public class MessageQueueService : IDisposable
    {
        /// <summary>
        /// 导出完成事件（保留接口兼容性）
        /// </summary>
        public event EventHandler<ExportNotification>? ExportCompleted;

        /// <summary>
        /// 通用通知事件（保留接口兼容性）
        /// </summary>
        public event EventHandler<string>? NotificationReceived;

        /// <summary>
        /// 开始监听消息（空实现，保留接口兼容性）
        /// </summary>
        public void StartListening()
        {
            // 后端会处理MQ消息，前端不需要监听
            System.Diagnostics.Debug.WriteLine("[MQ] 服务已启动，后端将处理MQ消息");
        }

        /// <summary>
        /// 停止监听消息（空实现，保留接口兼容性）
        /// </summary>
        public void StopListening()
        {
            System.Diagnostics.Debug.WriteLine("[MQ] 服务已停止");
        }

        /// <summary>
        /// 发送消息到队列（空实现，保留接口兼容性）
        /// </summary>
        public async Task<bool> SendMessageAsync(string message, string? topic = null)
        {
            await Task.Delay(10); // 最小延迟
            System.Diagnostics.Debug.WriteLine($"[MQ] 消息将由后端处理: {message}");
            return true;
        }

        /// <summary>
        /// 加入用户组（空实现，保留接口兼容性）
        /// </summary>
        public async Task<bool> JoinUserGroupAsync(string userId)
        {
            await Task.Delay(10);
            System.Diagnostics.Debug.WriteLine($"[MQ] 用户组操作将由后端处理: {userId}");
            return true;
        }

        /// <summary>
        /// 离开用户组（空实现，保留接口兼容性）
        /// </summary>
        public async Task<bool> LeaveUserGroupAsync(string userId)
        {
            await Task.Delay(10);
            System.Diagnostics.Debug.WriteLine($"[MQ] 用户组操作将由后端处理: {userId}");
            return true;
        }

        /// <summary>
        /// 释放资源
        /// </summary>
        public void Dispose()
        {
            // 无需释放资源
        }
    }

    /// <summary>
    /// 真实的SignalR服务实现
    /// 用于接收导出任务完成的实时通知
    /// </summary>
    public class SignalRService : IDisposable
    {
        private HubConnection? _connection;
        private readonly string _hubUrl;
        private bool _isConnected;

        public SignalRService(string hubUrl = "http://118.178.235.62:5672/fishNotificationHub")
        {
            _hubUrl = hubUrl;
        }

        /// <summary>
        /// 导出完成事件
        /// </summary>
        public event EventHandler<ExportNotification>? ExportCompleted;

        /// <summary>
        /// 通用通知事件
        /// </summary>
        public event EventHandler<string>? NotificationReceived;

        /// <summary>
        /// 连接状态变化事件
        /// </summary>
        public event EventHandler<bool>? ConnectionStateChanged;

        /// <summary>
        /// 建立SignalR连接
        /// </summary>
        public async Task<bool> ConnectAsync()
        {
            try
            {
                System.Diagnostics.Debug.WriteLine($"[SignalR] 开始连接到: {_hubUrl}");
                
                // 创建HubConnection
                _connection = new HubConnectionBuilder()
                    .WithUrl(_hubUrl, options =>
                    {
                        // 配置连接选项
                        options.AccessTokenProvider = () => Task.FromResult<string?>(null);
                        
                        // 添加更多配置选项
                        options.Transports = Microsoft.AspNetCore.Http.Connections.HttpTransportType.WebSockets | 
                                            Microsoft.AspNetCore.Http.Connections.HttpTransportType.LongPolling;
                        
                        // 增加超时时间
                        options.CloseTimeout = TimeSpan.FromSeconds(30);
                        
                        // 跳过SSL证书验证（仅用于测试，生产环境不建议）
                        options.HttpMessageHandlerFactory = (message) =>
                        {
                            if (message is HttpClientHandler clientHandler)
                                clientHandler.ServerCertificateCustomValidationCallback +=
                                    (sender, certificate, chain, sslPolicyErrors) => true;
                            return message;
                        };
                        
                        System.Diagnostics.Debug.WriteLine($"[SignalR] 连接选项配置完成");
                    })
                    .WithAutomaticReconnect(new[] { TimeSpan.Zero, TimeSpan.FromSeconds(2), TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(10) })
                    .ConfigureLogging(logging =>
                    {
                        // 启用详细日志（可选）
                        // logging.SetMinimumLevel(Microsoft.Extensions.Logging.LogLevel.Debug);
                    })
                    .Build();

                // 注册事件处理 - 优化重复监听问题
                _connection.On<ExportNotification>("ExportCompleted", notification =>
                {
                    System.Diagnostics.Debug.WriteLine($"[SignalR] 收到ExportCompleted通知: {notification.TaskId}");
                    ExportCompleted?.Invoke(this, notification);
                });

                // 只监听字符串形式的通用通知，避免重复处理
                _connection.On<string>("Notification", message =>
                {
                    System.Diagnostics.Debug.WriteLine($"[SignalR] 收到Notification字符串: {message}");
                    
                    // 检查是否是导出完成通知，如果是则跳过（由ExportCompleted处理）
                    if (message.Contains("ExportCompleted") || message.Contains("导出完成"))
                    {
                        System.Diagnostics.Debug.WriteLine($"[SignalR] 跳过重复的导出完成通知");
                        return;
                    }
                    
                    NotificationReceived?.Invoke(this, message);
                });

                // 移除对象形式的Notification监听器，避免重复处理
                /*
                _connection.On<object>("Notification", notificationObj =>
                {
                    System.Diagnostics.Debug.WriteLine($"[SignalR] 收到对象通知: {System.Text.Json.JsonSerializer.Serialize(notificationObj)}");
                    var message = System.Text.Json.JsonSerializer.Serialize(notificationObj);
                    NotificationReceived?.Invoke(this, message);
                });
                */

                // 测试用的Pong响应
                _connection.On<string>("Pong", message =>
                {
                    System.Diagnostics.Debug.WriteLine($"[SignalR] 收到Pong响应: {message}");
                    NotificationReceived?.Invoke(this, $"Pong: {message}");
                });

                // 连接状态变化处理
                _connection.Closed += async (error) =>
                {
                    _isConnected = false;
                    ConnectionStateChanged?.Invoke(this, false);
                    System.Diagnostics.Debug.WriteLine($"[SignalR] 连接已断开: {error?.Message}");
                };

                _connection.Reconnecting += (error) =>
                {
                    _isConnected = false;
                    ConnectionStateChanged?.Invoke(this, false);
                    System.Diagnostics.Debug.WriteLine($"[SignalR] 正在重连: {error?.Message}");
                    return Task.CompletedTask;
                };

                _connection.Reconnected += async (connectionId) =>
                {
                    _isConnected = true;
                    ConnectionStateChanged?.Invoke(this, true);
                    System.Diagnostics.Debug.WriteLine($"[SignalR] 重连成功: {connectionId}");
                    
                    // 重连后自动重新加入用户组
                    try
                    {
                        await _connection.InvokeAsync("JoinUserGroup", "demo-user-001");
                        System.Diagnostics.Debug.WriteLine("[SignalR] 重连后已重新加入用户组");
                    }
                    catch (Exception ex)
                    {
                        System.Diagnostics.Debug.WriteLine($"[SignalR] 重连后加入用户组失败: {ex.Message}");
                    }
                };

                // 启动连接
                System.Diagnostics.Debug.WriteLine("[SignalR] 正在启动连接...");
                await _connection.StartAsync();
                _isConnected = true;
                ConnectionStateChanged?.Invoke(this, true);
                System.Diagnostics.Debug.WriteLine($"[SignalR] 连接成功: {_connection.ConnectionId}");
                
                return true;
            }
            catch (Exception ex)
            {
                _isConnected = false;
                ConnectionStateChanged?.Invoke(this, false);
                System.Diagnostics.Debug.WriteLine($"[SignalR] 连接失败: {ex.Message}");
                System.Diagnostics.Debug.WriteLine($"[SignalR] 异常堆栈: {ex.StackTrace}");
                
                // 记录更详细的错误信息
                if (ex.InnerException != null)
                {
                    System.Diagnostics.Debug.WriteLine($"[SignalR] 内部异常: {ex.InnerException.Message}");
                }
                
                return false;
            }
        }

        /// <summary>
        /// 断开连接
        /// </summary>
        public async Task DisconnectAsync()
        {
            try
            {
                if (_connection != null)
                {
                    await _connection.StopAsync();
                    await _connection.DisposeAsync();
                    _connection = null;
                }
                _isConnected = false;
                ConnectionStateChanged?.Invoke(this, false);
                System.Diagnostics.Debug.WriteLine("[SignalR] 连接已断开");
            }
            catch (Exception ex)
            {
                System.Diagnostics.Debug.WriteLine($"[SignalR] 断开连接异常: {ex.Message}");
            }
        }

        /// <summary>
        /// 加入用户组
        /// </summary>
        public async Task<bool> JoinUserGroupAsync(string userId)
        {
            if (!_isConnected || _connection == null) return false;

            try
            {
                await _connection.InvokeAsync("JoinUserGroup", userId);
                System.Diagnostics.Debug.WriteLine($"[SignalR] 已加入用户组: {userId}");
                return true;
            }
            catch (Exception ex)
            {
                System.Diagnostics.Debug.WriteLine($"[SignalR] 加入用户组失败: {ex.Message}");
                return false;
            }
        }

        /// <summary>
        /// 离开用户组
        /// </summary>
        public async Task<bool> LeaveUserGroupAsync(string userId)
        {
            if (!_isConnected || _connection == null) return false;

            try
            {
                await _connection.InvokeAsync("LeaveUserGroup", userId);
                System.Diagnostics.Debug.WriteLine($"[SignalR] 已离开用户组: {userId}");
                return true;
            }
            catch (Exception ex)
            {
                System.Diagnostics.Debug.WriteLine($"[SignalR] 离开用户组失败: {ex.Message}");
                return false;
            }
        }

        /// <summary>
        /// 发送消息到服务器
        /// </summary>
        public async Task<bool> SendMessageAsync(string method, params object[] args)
        {
            if (!_isConnected || _connection == null) return false;

            try
            {
                await _connection.InvokeAsync(method, args);
                System.Diagnostics.Debug.WriteLine($"[SignalR] 发送消息成功: {method}");
                return true;
            }
            catch (Exception ex)
            {
                System.Diagnostics.Debug.WriteLine($"[SignalR] 发送消息失败: {ex.Message}");
                return false;
            }
        }

        /// <summary>
        /// 获取连接状态
        /// </summary>
        public bool IsConnected => _isConnected && _connection?.State == HubConnectionState.Connected;

        /// <summary>
        /// 获取连接ID
        /// </summary>
        public string? ConnectionId => _connection?.ConnectionId;

        public async void Dispose()
        {
            await DisconnectAsync();
        }
    }
}